/*
 * MoveDecision.fx
 *
 * Created on 2009-1-28, 14:42:00
 */

package util;

import javafx.util.Math;
import util.PacMan;
import util.Map;

/**
 
 */

public class MoveDecision {

   // x and y of an intended move
   public var x: Number;
   public var y: Number;

   public var xblink: Number;
   public var yblink: Number;

   public var score: Number;

   // evaluate if the move is valid,
   // if it is invalid, returns -1;
   // if it is valid, compute its score for ranking the final decision
   public function evaluate(pacMan: PacMan, isHollow: Boolean, personality: Integer ): Void {
      if ( x < 1 or y < 1 or y >= Map.HEIGHT - 1 or x >= Map.WIDTH - 1){
         score = -1;
         return ;
       }

      var status = Map.getCellData(x, y);
      if ( status == Map.BLOCK ) {
         score = -1;
         return ;
       }
      var distance;

      if(personality == 1){
            xblink = x;
            yblink = y;
            distance = Math.abs( x - pacMan.x ) + Math.abs( y - pacMan.y )
      }else if (personality == 2){
           if(pacMan.xDirection == -1 and pacMan.yDirection == 0)  //LEFT
              distance = Math.abs( x - (pacMan.x - 4)) + Math.abs( y - pacMan.y )
           else if (pacMan.xDirection == 1 and pacMan.yDirection == 0)  //RIGHT
              distance = Math.abs( x - (pacMan.x + 4)) + Math.abs( y - pacMan.y )
           else if (pacMan.xDirection == 0 and pacMan.yDirection == -1)  //UP
              distance = Math.abs( x - pacMan.x ) + Math.abs( y - (pacMan.y - 4))
           else if (pacMan.xDirection == 1 and pacMan.yDirection == 1)   //DOWN
              distance = Math.abs( x - pacMan.x ) + Math.abs( y - (pacMan.y + 4))
      }else if (personality == 3){
           if(pacMan.xDirection == -1 and pacMan.yDirection == 0){  //LEFT
              distance = Math.abs( x - (getTargetX(pacMan.x - 2, xblink))) + Math.abs( y - getTargetY(pacMan.y, yblink))
           }else if (pacMan.xDirection == 1 and pacMan.yDirection == 0){  //RIGHT
              distance = Math.abs( x - (getTargetX(pacMan.x + 2, xblink))) + Math.abs( y - getTargetY(pacMan.y, yblink))
           }else if (pacMan.xDirection == 0 and pacMan.yDirection == -1){  //UP
              distance = Math.abs( x - (getTargetX(pacMan.x, xblink))) + Math.abs( y - getTargetY(pacMan.y - 2, yblink))
           }else if (pacMan.xDirection == 1 and pacMan.yDirection == 1){   //DOWN
              distance = Math.abs( x - (getTargetX(pacMan.x, xblink))) + Math.abs( y - getTargetY(pacMan.y + 2, yblink))
           }
      }else if (personality == 4){
           if (inRange(pacMan.x,pacMan.y,)){
              if (isHollow){
                  distance = Math.abs( x - pacMan.x ) + Math.abs( y - pacMan.y );
              }else{
                  distance = 1 - distance;
              }
           }else
              distance = Math.abs( x - pacMan.x ) + Math.abs( y - pacMan.y )
      }


      if ( isHollow )
        score = 500 + distance  // mode to run away from Pac-Man
      else
        score = 500 - distance; // mode to chase Pac-Man
      // rank it as a default score
      
    }

    public function getTargetX(pacOffsetx: Integer, blinkX: Integer): Integer {
         var res = 0;
         if(pacOffsetx == blinkX){
             res = blinkX;
         } else if(pacOffsetx < blinkX){
              res = blinkX - (2 * blinkX);
              if(res < 1)
                  res = 1;
         } else {
              res = blinkX + blinkX;
              if(res >= Map.WIDTH - 2)
                  res = Map.WIDTH - 2
         }
         res
   }

    public function getTargetY(pacOffsety: Integer, blinkY: Integer): Integer {
         var res = 0;
         if(pacOffsety == blinkY){
             res = blinkY;
         } else if(pacOffsety < blinkY){
              res = blinkY - (2 * blinkY);
              if(res < 4)
                  res = 4;
         } else {
              res = blinkY + blinkY;
              if(res >= Map.HEIGHT - 4)
                  res = Map.HEIGHT - 4
         }
         res
   }

    public function inRange(pacx: Integer, pacy: Integer): Boolean {
         var res = false;
         if((x > pacx - 8 or x < pacx + 8)and(y > pacy - 8 or y < pacy + 8))
             res = true;
         res
   }
}